#!/usr/bin/env python3
"""
用户服务维护脚本
================

这个脚本提供了自动化的维护功能，包括：
1. 清理临时文件和缓存
2. 检查重复文件
3. 验证目录结构
4. 生成维护报告

使用方法：
    python scripts/user_service_maintenance.py [选项]

选项：
    --clean-cache    清理缓存文件
    --check-duplicates    检查重复文件
    --validate-structure    验证目录结构
    --full-maintenance    执行完整维护
    --report    生成维护报告
"""

import os
import sys
import shutil
import hashlib
import argparse
from pathlib import Path
from typing import List, Dict, Set, Tuple
from datetime import datetime
import json

class UserServiceMaintenance:
    """用户服务维护工具"""
    
    def __init__(self, service_path: str = "backend/services/user_service"):
        self.service_path = Path(service_path)
        self.report = {
            "timestamp": datetime.now().isoformat(),
            "actions": [],
            "warnings": [],
            "errors": [],
            "summary": {}
        }
    
    def clean_cache_files(self) -> None:
        """清理缓存文件和临时文件"""
        print("🧹 清理缓存文件...")
        
        cache_patterns = [
            "**/__pycache__",
            "**/*.pyc",
            "**/*.pyo",
            "**/.pytest_cache",
            "**/.coverage",
            "**/htmlcov",
            "**/*.egg-info",
            "**/build",
            "**/dist",
            "**/.DS_Store",
            "**/Thumbs.db",
            "**/*.tmp",
            "**/*.temp"
        ]
        
        cleaned_items = []
        
        for pattern in cache_patterns:
            for item in self.service_path.glob(pattern):
                try:
                    if item.is_file():
                        item.unlink()
                        cleaned_items.append(str(item))
                    elif item.is_dir():
                        shutil.rmtree(item)
                        cleaned_items.append(str(item))
                except Exception as e:
                    self.report["errors"].append(f"清理失败: {item} - {e}")
        
        self.report["actions"].append({
            "action": "clean_cache",
            "items_cleaned": len(cleaned_items),
            "files": cleaned_items[:10]  # 只记录前10个
        })
        
        print(f"✅ 已清理 {len(cleaned_items)} 个缓存文件/目录")
    
    def check_duplicate_files(self) -> Dict[str, List[str]]:
        """检查重复文件"""
        print("🔍 检查重复文件...")
        
        file_hashes = {}
        duplicates = {}
        
        # 排除的目录
        exclude_dirs = {".git", "__pycache__", ".pytest_cache", "htmlcov", "logs"}
        
        for file_path in self.service_path.rglob("*"):
            if (file_path.is_file() and 
                not any(excluded in file_path.parts for excluded in exclude_dirs)):
                
                try:
                    # 计算文件hash
                    with open(file_path, 'rb') as f:
                        file_hash = hashlib.md5(f.read()).hexdigest()
                    
                    if file_hash in file_hashes:
                        if file_hash not in duplicates:
                            duplicates[file_hash] = [file_hashes[file_hash]]
                        duplicates[file_hash].append(str(file_path))
                    else:
                        file_hashes[file_hash] = str(file_path)
                
                except Exception as e:
                    self.report["warnings"].append(f"无法读取文件: {file_path} - {e}")
        
        if duplicates:
            print(f"⚠️  发现 {len(duplicates)} 组重复文件:")
            for file_hash, files in duplicates.items():
                print(f"  - {files}")
        else:
            print("✅ 未发现重复文件")
        
        self.report["actions"].append({
            "action": "check_duplicates",
            "duplicate_groups": len(duplicates),
            "duplicates": duplicates
        })
        
        return duplicates
    
    def validate_directory_structure(self) -> bool:
        """验证目录结构"""
        print("📁 验证目录结构...")
        
        # 期望的目录结构
        expected_structure = {
            "api": "API路由层",
            "config": "配置管理",
            "containers": "依赖注入容器", 
            "core": "核心依赖",
            "database": "数据库管理",
            "deployment": "部署配置",
            "exceptions": "异常定义",
            "health": "健康检查",
            "interfaces": "接口定义",
            "repositories": "数据访问层",
            "schemas": "数据模式",
            "security": "安全组件",
            "services": "业务服务层",
            "tests": "测试代码",
            "utils": "工具函数",
            "validation": "数据验证",
            "user_service_Doc": "技术文档"
        }
        
        # 必需的文件
        required_files = [
            "main.py",
            "requirements.txt",
            "__init__.py",
            "conftest.py"
        ]
        
        structure_valid = True
        missing_dirs = []
        missing_files = []
        
        # 检查目录
        for dir_name, description in expected_structure.items():
            dir_path = self.service_path / dir_name
            if not dir_path.exists():
                missing_dirs.append(f"{dir_name} ({description})")
                structure_valid = False
        
        # 检查文件
        for file_name in required_files:
            file_path = self.service_path / file_name
            if not file_path.exists():
                missing_files.append(file_name)
                structure_valid = False
        
        if missing_dirs:
            print(f"⚠️  缺少目录: {missing_dirs}")
        if missing_files:
            print(f"⚠️  缺少文件: {missing_files}")
        
        if structure_valid:
            print("✅ 目录结构验证通过")
        
        self.report["actions"].append({
            "action": "validate_structure",
            "valid": structure_valid,
            "missing_dirs": missing_dirs,
            "missing_files": missing_files
        })
        
        return structure_valid
    
    def check_import_consistency(self) -> None:
        """检查导入一致性"""
        print("🔗 检查导入一致性...")
        
        import_issues = []
        
        # 检查__init__.py文件
        init_files = list(self.service_path.rglob("__init__.py"))
        
        for init_file in init_files:
            try:
                with open(init_file, 'r', encoding='utf-8') as f:
                    content = f.read()
                    
                # 检查是否有相对导入问题
                if "from ." in content:
                    lines = content.split('\n')
                    for i, line in enumerate(lines, 1):
                        if line.strip().startswith("from .") and "import" in line:
                            # 提取导入的模块名
                            parts = line.split("from .")[1].split(" import")[0].strip()
                            module_path = init_file.parent / f"{parts}.py"
                            
                            if not module_path.exists():
                                import_issues.append({
                                    "file": str(init_file),
                                    "line": i,
                                    "issue": f"导入的模块不存在: {parts}",
                                    "content": line.strip()
                                })
                            
            except Exception as e:
                self.report["warnings"].append(f"无法检查导入: {init_file} - {e}")
        
        if import_issues:
            print(f"⚠️  发现 {len(import_issues)} 个导入问题")
            for issue in import_issues[:5]:  # 只显示前5个
                print(f"  - {issue['file']}:{issue['line']} - {issue['issue']}")
        else:
            print("✅ 导入一致性检查通过")
        
        self.report["actions"].append({
            "action": "check_imports",
            "issues_found": len(import_issues),
            "issues": import_issues
        })
    
    def generate_maintenance_report(self) -> str:
        """生成维护报告"""
        print("📊 生成维护报告...")
        
        # 统计信息
        total_files = len(list(self.service_path.rglob("*.py")))
        total_dirs = len([d for d in self.service_path.rglob("*") if d.is_dir()])
        
        self.report["summary"] = {
            "total_python_files": total_files,
            "total_directories": total_dirs,
            "actions_performed": len(self.report["actions"]),
            "warnings_count": len(self.report["warnings"]),
            "errors_count": len(self.report["errors"])
        }
        
        # 生成报告文件
        report_file = f"user_service_maintenance_report_{datetime.now().strftime('%Y%m%d_%H%M%S')}.json"
        report_path = self.service_path / "logs" / report_file
        
        # 确保logs目录存在
        report_path.parent.mkdir(exist_ok=True)
        
        with open(report_path, 'w', encoding='utf-8') as f:
            json.dump(self.report, f, indent=2, ensure_ascii=False)
        
        print(f"✅ 维护报告已生成: {report_path}")
        return str(report_path)
    
    def full_maintenance(self) -> None:
        """执行完整维护"""
        print("🔧 开始完整维护...")
        print("=" * 50)
        
        self.clean_cache_files()
        print()
        
        self.check_duplicate_files()
        print()
        
        self.validate_directory_structure()
        print()
        
        self.check_import_consistency()
        print()
        
        report_path = self.generate_maintenance_report()
        
        print("=" * 50)
        print("🎉 完整维护完成!")
        print(f"📊 详细报告: {report_path}")


def main():
    """主函数"""
    parser = argparse.ArgumentParser(description="用户服务维护工具")
    parser.add_argument("--clean-cache", action="store_true", help="清理缓存文件")
    parser.add_argument("--check-duplicates", action="store_true", help="检查重复文件")
    parser.add_argument("--validate-structure", action="store_true", help="验证目录结构")
    parser.add_argument("--check-imports", action="store_true", help="检查导入一致性")
    parser.add_argument("--full-maintenance", action="store_true", help="执行完整维护")
    parser.add_argument("--report", action="store_true", help="生成维护报告")
    parser.add_argument("--service-path", default="backend/services/user_service", 
                       help="用户服务路径")
    
    args = parser.parse_args()
    
    # 检查服务路径是否存在
    service_path = Path(args.service_path)
    if not service_path.exists():
        print(f"❌ 用户服务路径不存在: {service_path}")
        sys.exit(1)
    
    maintenance = UserServiceMaintenance(args.service_path)
    
    if args.full_maintenance:
        maintenance.full_maintenance()
    else:
        if args.clean_cache:
            maintenance.clean_cache_files()
        
        if args.check_duplicates:
            maintenance.check_duplicate_files()
        
        if args.validate_structure:
            maintenance.validate_directory_structure()
        
        if args.check_imports:
            maintenance.check_import_consistency()
        
        if args.report:
            maintenance.generate_maintenance_report()
    
    if not any([args.clean_cache, args.check_duplicates, args.validate_structure, 
                args.check_imports, args.full_maintenance, args.report]):
        print("请指定至少一个操作选项，使用 --help 查看帮助")


if __name__ == "__main__":
    main()
